﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using DotNet.JCore.Entity;
using System.Threading.Tasks;
using DotNet.Collections;
using DotNet.Extensions;
using DotNet.Utility;
using DotNet.Helper;
using DotNet.Data;

namespace DotNet.JCore.Service
{
    /// <summary>
    /// 系统稽查登记服务
    /// </summary>
    public class SystemRegService
    {
        private JCoreRepository<SystemReg> repos = new JCoreRepository<SystemReg>();

        /// <summary>
        /// 是否存在指定名称的对象
        /// </summary>
        /// <param name="id">主键</param>
        /// <param name="name">名称</param>
        /// <returns>如果存在返回false</returns>
        public BoolMessage ExistsByName(string id, string name)
        {
            if (repos.Exists(p => p.CarNumber == name && p.Id != id))
            {
                return new BoolMessage(false, $"已经存在车号为: {name} 的登记");
            }
            return BoolMessage.True; ;
        }

        /// <summary>
        /// 保存
        /// </summary>
        /// <param name="entity">实体</param>
        /// <param name="isCreate">是否新增</param>
        public BoolMessage Save(SystemReg entity, bool isCreate)
        {
            var result = EntityHelper.ValidAsMessage(entity, "<br>");
            if (result.Failure)
            {
                return result;
            }
            result = ExistsByName(entity.Id, entity.CarNumber);
            if (result.Failure)
            {
                return result;
            }

            if (isCreate)
            {
                repos.Insert(entity);
            }
            else
            {
                repos.UpdateExclude(entity, p => p.CreateId, p => p.CreateName, p => p.CreateTime);
            }
            return BoolMessage.True;
        }

        /// <summary>
        /// 删除对象
        /// </summary>
        /// <param name="ids">主键数组</param>
        public BoolMessage Delete(string[] ids)
        {
            repos.Delete(ids);
            return BoolMessage.True;
        }

        /// <summary>
        /// 获取对象
        /// </summary>
        /// <param name="id">主键</param>
        public SystemReg Get(string id)
        {
            return repos.Get(id);
        }

        /// <summary>
        /// 获取对象
        /// </summary>
        /// <param name="userId">账号主键</param>
        public SystemReg GetBySystemRegId(string Id)
        {
            return repos.Get(p => p.Id == Id);
        }

        /// <summary>
        /// 获取启用的简单对象集合(已排序)
        /// </summary>
        public List<Simple> GetSimpleList()
        {
            var query = repos.SQL
                .OrderByDesc(p => p.CreateTime)
                .Select(p => p.Id, p => p.CarNumber);

            return repos.Fetch(query).
                Select(p => new Simple(p.Id, p.CarNumber, SpellHelper.GetSpell(p.CarNumber)))
                .ToList();
        }

        /// <summary>
        /// 获取启用的对象集合(已排序)
        /// </summary>
        /// <param name="name">名称关键字</param>
        /// <param name="enabled">有限</param>
        /// <param name="pointId">检查点</param>
        public List<SystemReg> GetList(string name, string Point, string Station, bool? CheckStatus, string createname, DateTime? startDate, DateTime? endDate)
        {
            var query = repos.SQL.OrderByDesc(p => p.CreateTime);
            SetQuery(query, name, Point,Station, CheckStatus, createname, startDate,endDate);
            return repos.Fetch(query);
        }

        /// <summary>
        /// 获取对象分页集合
        /// </summary>
        /// <param name="pageCondition">分页对象</param>
        /// <param name="name">名称关键字</param>
        /// <param name="enabled">有限</param>
        /// <param name="pointId">检查点</param>
        public PageList<SystemReg> GetPageList(PaginationCondition pageCondition,
            string name, string Point, string Station, bool? CheckStatus,string CreateId, DateTime? startDate, DateTime? endDate)
        {
            pageCondition.SetDefaultOrder(nameof(SystemReg.ExitTime));
            var query = repos.PageQuery(pageCondition);
            SetQuery(query, name, Point, Station, CheckStatus, CreateId, startDate,endDate);
            query.ExcludeSelect(p => p.Note);
            return repos.Page(query);
        }

        /// <summary>
        /// 设置查询条件
        /// </summary>
        /// <param name="query">查询对象</param>
        /// <param name="search">数据对象</param>
        public void SetQuery(SQLQuery<SystemReg> query, string name, string Point, string Station, bool? CheckStatus,string CreateId, DateTime? startDate, DateTime? endDate)
        {
            if ( name.IsNotEmpty())
            {
                name = name.Trim();
                query.Where(p => p.CarNumber.Contains(name));
            }
            if (Point.IsNotEmpty())
            {
                Point = Point.Trim();
                query.Where(p => p.PointId.Contains(Point));
            }
            if (Station.IsNotEmpty())
            {
                Station = Station.Trim();
                query.Where(p => p.StationID.Contains(Station));
            }
            if (CheckStatus.IsNotEmpty() )
            {
                query.Where(p => p.CheckStatus == CheckStatus.Value);
            }
            if(CreateId.IsNotEmpty() && CreateId.Trim() != "0")
                {
                CreateId = CreateId.Trim();
                query.Where(p=>p.CreateId== CreateId);
            }
            if (startDate.HasValue)
            {
                var startDateDt = startDate.ToDateTime();
                query.Where(p => p.ExitTime >= startDateDt);
            }

            if (endDate.HasValue)
            {
                var endDateDt = endDate.ToDateTime().AddDays(1);
                query.Where(p => p.ExitTime <= endDateDt);
            }
        }


        #region
        /// <summary>
        /// 
        /// </summary>
        /// <param name="carNO"></param>
        /// <param name="startDate"></param>
        /// <returns></returns>
        public List<SystemReg> GetList( string carNO, DateTime? startDate)
        {
            var query = repos.SQL.OrderByDesc(p => p.CreateTime);
            SetQuery(query, carNO, startDate);
            return repos.Fetch(query);
        }

        /// <summary>
        /// 设置查询条件
        /// </summary>
        /// <param name="query">查询对象</param>
        /// <param name="search">数据对象</param>
        public void SetQuery(SQLQuery<SystemReg> query, string carNO,  DateTime? startDate)
        {
            if (carNO.IsNotEmpty())
            {
                carNO = carNO.Trim();
                query.Where(p => p.CarNumber.Contains(carNO));
            }
            else
            {
                query.Where(p=>p.CarNumber=="");
            }
            if (startDate.HasValue)
            {
                var startDateDt = startDate.ToDateTime();
                query.Where(p => p.ExitTime >= startDateDt);
            }
            else
            {
                query.Where(p => p.ExitTime == null);
            }
        }

        /// <summary>
        ///  合并系统登记和人工登记
        /// </summary>
        /// <param name="carNO"></param>
        /// <param name="startDate"></param>
        /// <returns></returns>
        public List<SystemReg> GetAllList(string carNO, DateTime? startDate)
        {
            var startDateDt = System.DateTime.Now;
            string str_where = "WHERE 1=1 ";
            string str_where1 = "WHERE 1=1 ";
            if (carNO.IsNotEmpty() && !ValidateHelper.IsStringRegExMatch(carNO, true, "[`~!@#$%^&*()+=|{}':;',\\[\\].<>/?~！@#￥%……&*（）——+|{}【】‘；：”“’。，、？]"))
            {
                str_where += " AND CarNumber LIKE '%" + carNO + "%'";
                str_where1 += " AND CarNumber LIKE '%" + carNO + "%'";
            }
            else
            {
                str_where += " AND CarNumber is null";
                str_where1 += " AND CarNumber is null";
            }
            if (startDate.HasValue)
            {
                startDateDt = startDate.ToDateTime();
                str_where += " AND ExitTime >= @StartDate";
                str_where1 += " AND CreateTime >= @StartDate";
            }
            else
            {
                str_where += " AND ExitTime IS NULL ";
                str_where1 += " AND CreateTime IS NULL ";
            }
            StringBuilder sb = new StringBuilder();
            sb.Append("select id,CarNumber,ExitTime,station,ExitNumber,PassengerNumber,DriverName,DriverPhone,Line,Corp,RunSecond,RunStatus,RegType," +
                "CheckStatus,ProcessStatus,OffenceId,OffenceName,PointId,PointName,Enabled,CreateId,CreateName,CreateTime,Note,SeatCount,StationId " +
                "from dbo.SystemReg ");
            sb.Append(str_where);
            sb.Append(" UNION ");
            sb.Append("select id,CarNumber,'',StationName,ExitNumber,PassengerNumber,DriverName,DriverPhone,Line,Corp,'','',RegType," +
                "CheckStatus,ProcessStatus,OffenceId,OffenceName,PointId,PointName,Enabled,CreateId,CreateName,CreateTime,Note,'',station" +
                " from dbo.ManualReg ");
            sb.Append(str_where1);
            return repos.Database.Query<SystemReg>(sb.ToString(),new { StartDate= startDateDt }).ToList();
        }
        #endregion
    }
}
